package scala.com.shujia.jichu

/**
 * scala中的集合：
 * List: 元素有序，且可以发生重复，长度固定的
 * Set:  元素无序，且唯一，长度固定的
 * Map:  元素是键值对的形式，键是唯一的
 * Tuple: 元组，长度是固定的，每个元素的数据类型可以不一样
 */
object Demo14List {
  def main(args: Array[String]): Unit = {
    //创建一个scala中的List集合
    //创建了一个空集合
    //    val list1: List[Nothing] = List()
    val list2: List[Int] = List(34, 11, 22, 11, 33, 44, 55, 22, 75, 987, 1, 12, 34, 66, 77)

    println(list2)
    //获取List集合的长度
    println(list2.size)
    println(list2.length)
    println("=" * 50)
    //可以直接通过索引下标获取元素
    println(list2(0))
    println(list2(1))
    println(list2(2))
    println("=" * 50)
    //scala推荐获取第一个元素的方式是调用head函数
    println(list2.head)
    println(list2.last)
    //根据指定的分隔符拼接元素
    println(list2.mkString("|"))
    println("=" * 50)
    val resList1: List[Int] = list2.reverse //返回一个新的集合
    println(s"list2:$list2")
    println(s"resList1:$resList1")
    println("=" * 50)
    val resList2: List[Int] = list2.distinct //返回一个新的集合
    println(s"list2:$list2")
    println(s"resList2:$resList2")
    println("=" * 50)
    val resList3: List[Int] = list2.tail // 除去第一个，其余的元素返回一个新的集合
    println(s"list2:$list2")
    println(s"resList3:$resList3")
    println("=" * 50)
    val resList4: List[Int] = list2.take(5) // 从左向右取元素，取若干个
    println(s"list2:$list2")
    println(s"resList4:$resList4")
    println("=" * 50)
    val resList5: List[Int] = list2.takeRight(5) //取右边的几个，组成新的集合
    println(s"list2:$list2")
    println(s"resList5:$resList5")
    println("=" * 50)
    //从第一个判断取数据，直到不符合条件停止
    val resList10: List[Int] = list2.takeWhile((e: Int) => e % 2 == 0)
    println(s"list2:$list2")
    println(s"resList10:$resList10")
    println("***********************************" * 50)
    val res1: Int = list2.sum // 元素必须是数值
    println(s"集合中的元素和为：$res1")
    println("=" * 50)
    val res2: Int = list2.max
    println(s"集合中的元素最大值为：$res2")
    println("=" * 50)
    //集合的遍历
    for (e <- list2) {
      println(e)
    }
    println("=" * 50)

    /**
     * 高阶函数:
     * foreach: 将集合中的元素依次取出传入到后面的函数中
     * 注意：没有返回值的，要么就输出，要么就其他方式处理掉了
     */
    //def foreach[U](f: A => U)
    //    list2.foreach((e: Int) => println(e))
    //    list2.foreach(println)
    //需求1：使用foreach求出集合中偶数的和
    var ouSum = 0
    var jiSum = 0
    list2.foreach((e: Int) => {
      if (e % 2 == 0) {
        ouSum += e
      } else {
        jiSum += e
      }
    })
    println(s"集合中偶数之和为：$ouSum")
    println(s"集合中奇数之和为：$jiSum")
    println("=" * 50)
    /**
     * 高阶函数:
     * map: 依次处理每一个元素，得到一个新的结果，返回到一个新的集合中
     */
    val list3: List[Int] = List(1, 2, 3, 4, 5, 6, 7, 8, 9)
    //需求2：将集合中的每一个元素*2
    val resList6: List[Int] = list3.map((e: Int) => e * 2)
    println(s"list3:$list3")
    println(s"resList6:$resList6")

    /**
     * 高阶函数:
     * filter: 保留符合条件的元素
     */
    println("=" * 50)
    val list4: List[Int] = List(4, 7, 9, 10, 12, 11, 14, 9, 7)
    val resList7: List[Int] = list4.filter((e: Int) => e % 2 == 0)
    println(s"list4:$list4")
    println(s"resList7:$resList7")

    /**
     * 高阶函数:
     * sortBy: 排序
     * sortWith: 两个数之间的关系排序
     */
    println("=" * 50)
    val resList8: List[Int] = list4.sortBy((e: Int) => -e)
    println(s"list4:$list4")
    println(s"resList8:$resList8")
    val resList9: List[Int] = list4.sortWith((x: Int, y: Int) => x > y)
    println(s"list4:$list4")
    println(s"resList9:$resList9")

    /**
     * 高阶函数:
     * flatMap: 扁平化
     */
    println("=" * 50)
    val list5: List[String] = List("hello|world|java", "hello|hadoop|flink", "scala|spark|hadoop")
    val resTmp1: List[String] = list5.flatMap((e: String) => e.split("\\|"))
    resTmp1.foreach(println)

    /**
     * 高阶函数:
     * groupBy: 分组
     */
    val list6: List[String] = List("hello", "world", "java", "hadoop", "flink", "java", "hadoop", "flink", "flink", "java", "hadoop", "flink", "java", "hadoop", "hello", "world", "java", "hadoop", "hello", "world", "java", "hadoop")
    val map: Map[String, List[String]] = list6.groupBy((e: String) => e)
    for (e <- map) {
      println(e)
    }

    /**
     * 基本函数
     *
     * 高阶函数：
     *  foreach: 依次取出元素，进行后面函数逻辑，没有返回值
     *  map: 依次取出元素，进行后面函数逻辑，有返回值，返回新的集合
     *  filter: 所有数据中取出符合条件的元素
     *  sortBy/sortWith: 排序
     *  flatMap: 扁平化
     *  groupBy: 分组，结果是一个map集合
     */

  }
}
